﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using SoftwareConsulting.BI11.Studio.Core.Project;
using SoftwareConsulting.BI11.Studio.Core.Project.Metadata;
using SoftwareConsulting.BI11.Studio.Core.Project.SituationsHierarchy;
using SoftwareConsulting.BI11.Studio.Core.Project.SituationsHierarchy.RulesContainers;
using SoftwareConsulting.BI11.Studio.InternalServices;
using SoftwareConsulting.BI11.Studio.UI.Properties;

namespace SoftwareConsulting.BI11.Studio.UI.ProjectExplorer.SituationsHierarchy.RulesContainers
{
    /// <summary>
    /// Класс диалога редактирования контейнера правил
    /// </summary>
    public partial class EditRuleDialog : RestorableForm
    {
        private int _selectedConditionPosition; //позиция выделенного условия посылки               
        private int _selectedConclusionCommandPosition; //позиция выделенной команды заключения
        private Guid _owningRulesContainerId; //идентификатор редактируемого контейнера правил
        private Guid _owningSituationId; //идентификатор редактируемой ситуации
        private SoftwareConsulting.BI11.Studio.Core.Project.SituationsHierarchy.RulesContainers.Rule _rule; //редактируемое правило
        private ProjectDescriptor _projectLink; //для связи с проектом
        private ProjectExplorerForm _projectExplorerLink;
        private bool programdirty = false;

        /// <summary>
        /// Геттер-сеттер позиции выделенной команды заключения
        /// </summary>
        private int SelectedConclusionCommandPosition
        {
            get
            {
                return _selectedConclusionCommandPosition;
            }
            set
            {
                _selectedConclusionCommandPosition = value;
                DeleteCommandButton.Enabled = (_selectedConclusionCommandPosition != -1) ? true : false;
                UpCommandButton.Enabled = (_selectedConclusionCommandPosition > 0) ? true : false;
                DownCommandButton.Enabled = ((_selectedConclusionCommandPosition != -1) && (_selectedConclusionCommandPosition < (ConclusionCommandsDataGrid.Rows.Count - 1))) ? true : false;
            }
        }

        /// <summary>
        /// Геттер-сеттер позиции выделенного условия посылки
        /// </summary>
        private int SelectedConditionPosition
        {
            get
            {
                return _selectedConditionPosition;
            }
            set
            {
                _selectedConditionPosition = value;
                DeleteConditionButton.Enabled = (_selectedConditionPosition != -1) ? true : false;
                UpConditionButton.Enabled = (_selectedConditionPosition > 0) ? true : false;
                DownConditionButton.Enabled = ((_selectedConditionPosition != -1) && (_selectedConditionPosition < (ConditionsDataGrid.Rows.Count - 1))) ? true : false;
            }
        }

        /// <summary>
        /// Геттер посылки нового правила
        /// </summary>
        private IReason _reason
        {
            get
            {
                return _rule.Reason;
            }
        }

        /// <summary>
        /// Геттер заключения нового правила
        /// </summary>
        private IConclusion _conclusion
        {
            get
            {
                return _rule.Conclusion;
            }
        }

        /// <summary>
        /// Геттер редактируемого контейнера правил
        /// </summary>
        private RulesContainer _owningRulesContainer
        {
            get
            {
                return _projectLink.GetRulesContainerById(_owningRulesContainerId);
            }
        }

        /// <summary>
        /// Геттер редактируемой ситуации
        /// </summary>
        private Situation _owningSituation
        {
            get
            {
                return _projectLink.GetItemById(_owningSituationId);
            }
        }

        /// <summary>
        /// Инициализация компонентов
        /// </summary>
        public EditRuleDialog(Guid newOwningSituationId, SoftwareConsulting.BI11.Studio.Core.Project.SituationsHierarchy.RulesContainers.Rule editingRule, ProjectExplorerForm projectExplorerLink)
        {
            _projectExplorerLink = projectExplorerLink;
            _selectedConditionPosition = -1;
            _selectedConclusionCommandPosition = -1;
            _projectLink = _projectExplorerLink.ProjectLink;
            _rule = editingRule;
            _owningRulesContainerId = _rule.Container.Id;
            _owningSituationId = newOwningSituationId;            
            InitializeComponent();
        }

        /// <summary>
        /// Подготавливает список доступных элементов
        /// </summary>
        /// <param name="leftPath"></param>
        /// <returns></returns>
        private ICollection<string> PrepareElementsList(PathToValue leftPath, Guid withSituationId, bool withIndicators, PathToValue thisPath)
        {            
            ICollection<string> items = new List<string>();
            IndicatorType indt = leftPath == null ? IndicatorType.None : leftPath.IndicatorType;
            items = _projectLink.GetAllCharacteristicsForRulesContainerEditor(indt, withSituationId);
            if (withIndicators)
            {                
                foreach(IMetadataObjectDescriptor desc in _projectLink.RepositoryLink.GetObjectsDescriptors(MetadataObjectKind.Indicator))
                {
                    IndicatorType it = (IndicatorType)desc.Subkind;
                    if ((Indicator.IsUserType(it) || Indicator.IsLogicalType(it)) && ((indt == IndicatorType.None) || (Indicator.AreComparableTypes(indt, it))))
                    {
                        IIndicator ind = desc.Bind() as IIndicator;
                        int ic = ind.GetIndicatorValuesCount();
                        for (int i = 0; i < ic; i++)
                        {
                            IndicatorValue iv = ind.GetIndicatorValueByPosition(i);
                            items.Add(iv.ToStringWithIndicator());
                        }
                    }
                }
            }
            if (thisPath.Kind == PathToValueKind.DateAndFactCorrelationsCharacteristic)
            {
                items.Add(thisPath.ToStringUsingWithSituation(withSituationId));
            }
            return items;
        }

        /// <summary>
        /// Заполняет комбобокс допустимыми элементами
        /// </summary>
        /// <param name="leftPath"></param>
        /// <param name="combo"></param>
        private void FillElement(PathToValue leftPath, DataGridViewComboBoxCell combo, Guid withSituationId, bool withIndicators, PathToValue thisPath)
        {
            programdirty = true;
            combo.Value = null;
            programdirty = false;
            DataGridViewComboBoxCell.ObjectCollection items = combo.Items;
            items.Clear();
            items.AddRange(PrepareElementsList(leftPath, withSituationId, withIndicators, thisPath).ToArray());
        }

        /// <summary>
        /// Заполняет комбобокс допустимыми знаками сравнения
        /// </summary>
        /// <param name="combo"></param>
        private void FillSign(PathToValue leftPath, PathToValue rightPath, DataGridViewComboBoxCell combo)
        {
            programdirty = true;
            combo.Value = null;
            programdirty = false;
            DataGridViewComboBoxCell.ObjectCollection items = combo.Items;
            items.Clear();
            items.Add(Condition.SignToString(ConditionSigns.EqualsSign));
            items.Add(Condition.SignToString(ConditionSigns.NotEquals));
            bool numeric = true;
            bool tableorcube = false;
            switch (leftPath.Kind)
            {
                case PathToValueKind.IndicatorValue:                    
                case PathToValueKind.NormalCharacteristic:
                    break;
                case PathToValueKind.TableCharacteristic:
                case PathToValueKind.DateAndFactCorrelationsCharacteristic:
                    tableorcube = true; //любой тип катит
                    break;
            }
            if (!tableorcube)
            {
                switch (rightPath.Kind)
                {
                    case PathToValueKind.IndicatorValue:
                    case PathToValueKind.NormalCharacteristic:
                        break;
                    case PathToValueKind.TableCharacteristic:
                    case PathToValueKind.DateAndFactCorrelationsCharacteristic:
                        tableorcube = true;//любой тип катит
                        break;
                }
            }
            if ((numeric) && (tableorcube))            
            {
                items.Add(Condition.SignToString(ConditionSigns.Less));
                items.Add(Condition.SignToString(ConditionSigns.LessOrEquals));
                items.Add(Condition.SignToString(ConditionSigns.More));
                items.Add(Condition.SignToString(ConditionSigns.MoreOrEquals));
            }
        }

        /// <summary>
        /// Заполняет комбобокс всеми возможными операциями
        /// </summary>
        /// <param name="combo"></param>
        private void FillOperation(DataGridViewComboBoxCell combo, bool isFirst)
        {
            programdirty = true;
            combo.Value = null;
            programdirty = false;
            DataGridViewComboBoxCell.ObjectCollection items = combo.Items;
            items.Clear();
            items.Add(Reason.ConnectionToString(ConnectionKind.And));
            if (!isFirst)
            {
                items.Add(Reason.ConnectionToString(ConnectionKind.Or));
            }
        }

        /// <summary>
        /// Обновление информации о команде заключения создаваемого правила
        /// </summary>
        private void RefreshConclusionCommand(int index)
        {
            IConclusionCommand comm = _conclusion.GetItemByPosition(index);
            PathToValue leftpath = comm.PathToLeftValue;
            PathToValue rightpath = comm.PathToRightValue;            
            DataGridViewRow row = ConclusionCommandsDataGrid.Rows[index];
            DataGridViewCellCollection cells = row.Cells;
            //левый элемент                
            DataGridViewComboBoxCell dvc = cells[1] as DataGridViewComboBoxCell;
            FillElement(null, dvc, Guid.Empty, false, leftpath);
            string s = leftpath.ToStringUsingWithSituation(Guid.Empty);
            if (!dvc.Items.Contains(s))
            {
                s = dvc.Items[0].ToString();                
                leftpath.ParseElementAndApply(s, Guid.Empty, null);
            }
            dvc.Value = s;
            //правый элемент                
            dvc = cells[3] as DataGridViewComboBoxCell;
            FillElement(leftpath, dvc, Guid.Empty, true, rightpath);
            s = rightpath.ToStringUsingWithSituation(Guid.Empty);
            if (!dvc.Items.Contains(s))
            {
                s = dvc.Items[0].ToString();                
                rightpath.ParseElementAndApply(s, Guid.Empty, null);
            }
            dvc.Value = s;
            //знак действия
            DataGridViewTextBoxCell dvt = cells[2] as DataGridViewTextBoxCell;
            dvt.Value = ConclusionCommand.AssignmentSignToString();
        }

        /// <summary>
        /// Обновление информации об условии создаваемого правила
        /// </summary>
        private void RefreshCondition(int index)
        {
            ICondition cond = _reason.GetItemByPosition(index);
            PathToValue leftpath = cond.PathToLeftValue;
            PathToValue rightpath = cond.PathToRightValue;            
            ConnectionKind conn = _reason.GetConnectionByIndex(index);
            DataGridViewRow row = ConditionsDataGrid.Rows[index];
            DataGridViewCellCollection cells = row.Cells;            
            //левый элемент                
                DataGridViewComboBoxCell dvc = cells[1] as DataGridViewComboBoxCell;
                FillElement(null, dvc, _reason.WithSituationId, true, leftpath);
                string s = leftpath.ToStringUsingWithSituation(_reason.WithSituationId);
                if (!dvc.Items.Contains(s))
                {                    
                    s = dvc.Items[0].ToString();                    
                    leftpath.ParseElementAndApply(s, _reason.WithSituationId, null);
                }
                dvc.Value = s;                
            //правый элемент                
                dvc = cells[3] as DataGridViewComboBoxCell;
                FillElement(leftpath, dvc, _reason.WithSituationId, true, rightpath);
                s = rightpath.ToStringUsingWithSituation(_reason.WithSituationId);
                if (!dvc.Items.Contains(s))
                {
                    s = dvc.Items[0].ToString();                    
                    rightpath.ParseElementAndApply(s, _reason.WithSituationId, null);
                }
                dvc.Value = s;
            //отношение
                dvc = cells[2] as DataGridViewComboBoxCell;
                FillSign(leftpath, rightpath, dvc);
                cond.Sign = cond.Sign; //для обеспечения корректности знака
                dvc.Value = Condition.SignToString(cond.Sign);      
            //операция
                dvc = cells[4] as DataGridViewComboBoxCell;
                FillOperation(dvc, index==0);
                dvc.Value = Reason.ConnectionToString(conn);
        }

        /// <summary>
        /// Обновление информации о текущих условиях редактируемого правила
        /// </summary>
        private void RefreshConditions()
        {
            //заполняем комбик With
            ComboBox.ObjectCollection items = WithComboBox.Items;
            items.Clear();
            items.Add("");            
            foreach(Situation sit in _projectLink)
            {
                Characteristic ch = sit.GetFirstCharacteristicByIndicatorType(IndicatorType.DateAndFactCorrelations);
                ch = ch != null ? ch : sit.GetFirstCharacteristicByIndicatorType(IndicatorType.Table);
                if (ch != null)
                {
                    items.Add(sit.ToString());
                }
            }
            if (_reason.WithSituationId != Guid.Empty)
            {
                programdirty = true;
                WithComboBox.SelectedItem = _projectLink.GetItemById(_reason.WithSituationId).ToString();
                programdirty = false;
            }
            //заполняем условия посылки
            DataGridViewRowCollection rows = ConditionsDataGrid.Rows;
            rows.Clear();
            int c = _reason.ItemsCount;            
            for (int i = 0; i < c; i++)
            {                
                rows.Add();
                RefreshCondition(i);
            }
        }

        /// <summary>
        /// Обновление информации о текущих командах заключения редактируемого правила
        /// </summary>
        private void RefreshConclusionCommands()
        {            
            ConclusionCommandsDataGrid.Rows.Clear();
            int c = _conclusion.ItemsCount;
            for (int i = 0; i < c; i++)
            {
                ConclusionCommandsDataGrid.Rows.Add();
                RefreshConclusionCommand(i);
            }
        }

        /// <summary>
        /// Добавление нового условия в конец списка условий
        /// </summary>
        private void AddCondition()
        {
            IIndicator boolIndicator = _projectLink.GetSpecialIndicator(IndicatorType.Boolean, true);
            //если использовать один и тот же ptv, то и левая и правая часть будут одним и тем же            
            PathToValue ptv = new PathToValue(PathToValueKind.IndicatorValue, boolIndicator.GetIndicatorValueByPosition(0).Id, _projectLink);
            PathToValue ptv2 = new PathToValue(PathToValueKind.IndicatorValue, boolIndicator.GetIndicatorValueByPosition(0).Id, _projectLink);            
            var cond = new Condition(_projectLink, ptv, ptv2, _reason);
            _reason.Add(cond);
            DataGridViewRowCollection rows = ConditionsDataGrid.Rows;
            rows.Add();            
            RefreshCondition(_reason.ItemsCount - 1);
            SelectCondition(rows.Count - 1);
        }

        /// <summary>
        /// Добавление новой команды заключения в конец списка команд
        /// </summary>
        private void AddConclusionCommand()
        {            
            PathToValue ptv = null;
            PathToValue ptv2 = null;
            Characteristic sl = _projectLink.GetAnyCharacteristicForRulesContainer();
            //если использовать один и тот же ptv, то и левая и правая часть будут одним и тем же            
            ptv = new PathToValue(PathToValueKind.NormalCharacteristic, sl.Name, _projectLink);
            ptv2 = new PathToValue(PathToValueKind.NormalCharacteristic, sl.Name, _projectLink);                            
            ConclusionCommand comm = new ConclusionCommand(_projectLink, ptv, ptv2, _conclusion);
            _conclusion.Add(comm);
            DataGridViewRowCollection rows = ConclusionCommandsDataGrid.Rows;
            rows.Add();
            RefreshConclusionCommand(_conclusion.ItemsCount - 1);
            SelectConclusionCommand(rows.Count - 1);
        }

        /// <summary>
        /// Удаление выбранной комманды заключения
        /// </summary>
        private void DeleteConclusionCommand()
        {
            _conclusion.DeleteByPosition(SelectedConclusionCommandPosition);
            RefreshConclusionCommands();
            int c = _conclusion.ItemsCount;
            if ((c > 0) && (SelectedConclusionCommandPosition < c))
            {
                SelectConclusionCommand(SelectedConclusionCommandPosition);
            }
            else
            {
                SelectedConclusionCommandPosition = -1;
            }
        }

        /// <summary>
        /// Удаление выбранного условия
        /// </summary>
        private void DeleteCondition()
        {
            _reason.DeleteByPosition(SelectedConditionPosition);
            RefreshConditions();
            int c = _reason.ItemsCount;
            if ((c > 0)&&(SelectedConditionPosition<c))            
            {
                SelectCondition(SelectedConditionPosition);
            }
            else
            {
                SelectedConditionPosition = -1;
            }
        }

        /// <summary>
        /// Поднимает выбранное условие вверх
        /// </summary>
        private void UpCondition()
        {
            int topos = _selectedConditionPosition - 1;
            _reason.SwapItems(_reason.GetItemByPosition(_selectedConditionPosition), _reason.GetItemByPosition(topos));
            RefreshCondition(_selectedConditionPosition);
            RefreshCondition(topos);
            SelectCondition(topos);
        }

        /// <summary>
        /// Опускает выбранное условие вниз
        /// </summary>
        private void DownCondition()
        {
            int topos = _selectedConditionPosition + 1;
            _reason.SwapItems(_reason.GetItemByPosition(_selectedConditionPosition), _reason.GetItemByPosition(topos));
            RefreshCondition(_selectedConditionPosition);
            RefreshCondition(topos);
            SelectCondition(topos);
        }

        /// <summary>
        /// Поднимает выбранную команду заключения вверх
        /// </summary>
        private void UpConclusionCommand()
        {
            int topos = _selectedConclusionCommandPosition - 1;
            _conclusion.SwapItems(_conclusion.GetItemByPosition(_selectedConclusionCommandPosition), _conclusion.GetItemByPosition(topos));
            RefreshConclusionCommand(_selectedConclusionCommandPosition);
            RefreshConclusionCommand(topos);
            SelectConclusionCommand(topos);
        }

        /// <summary>
        /// Опускает выбранную команду заключения вниз
        /// </summary>
        private void DownConclusionCommand()
        {
            int topos = _selectedConclusionCommandPosition + 1;
            _conclusion.SwapItems(_conclusion.GetItemByPosition(_selectedConclusionCommandPosition), _conclusion.GetItemByPosition(topos));
            RefreshConclusionCommand(_selectedConclusionCommandPosition);
            RefreshConclusionCommand(topos);
            SelectConclusionCommand(topos);
        }

        /// <summary>
        /// Обновление текущей информации о редактируемом правиле
        /// </summary>
        private void RefreshInfo()
        {
            RefreshConditions();            
            NewCommandButton.Enabled = (_projectLink.GetAnyCharacteristicForRulesContainer() != null);
            RefreshConclusionCommands();
        }

        /// <summary>
        /// Обработка изменения значения в одном из комбиков датагрида условий
        /// </summary>
        private void ProcessConditionsDataGridDirty()
        {
            if (!programdirty)
            {
                programdirty = true;
                ConditionsDataGrid.EndEdit();
                programdirty = false;
                DataGridViewCell dvc_ = ConditionsDataGrid.CurrentCell;
                DataGridViewComboBoxCell dvc = dvc_ as DataGridViewComboBoxCell;
                int index = dvc.RowIndex;
                ICondition cond = _reason.GetItemByPosition(index);                
                string s = dvc.Value as string;
                PathToValue leftpath = cond.PathToLeftValue;
                PathToValue rightpath = cond.PathToRightValue;                                                
                switch (dvc.ColumnIndex)
                {                    
                    case 1:
                        //левый элемент                                                                            
                        if (s.Equals(leftpath.ToStringUsingWithSituation(_reason.WithSituationId)))                        
                            break;
                        FixedDimensionItemsPointer cip = leftpath.ParseElementAndApply(s, _reason.WithSituationId, null);
                        if (cip != null)                        
                        {                            
                            cip = _projectExplorerLink.MainFormLink.HierarchyForm.ShowFixedDimensionItemsDialog(cip);
                            Assert.FailIfNot(leftpath.ParseElementAndApply("", Guid.Empty, cip) == null, Assert.Id.Assert00184);
                        }
                        ConditionsDataGrid.EndEdit();
                        ConditionsDataGrid.CurrentCell = null;
                        break;
                    case 2:                    
                        //отношение                
                        cond.Sign = Condition.ParseSign(s);
                        break;                    
                    case 3:
                        //правый элемент    
                        if (s.Equals(rightpath.ToStringUsingWithSituation(_reason.WithSituationId)))
                            break;
                        FixedDimensionItemsPointer cip2 = rightpath.ParseElementAndApply(s, _reason.WithSituationId, null);
                        if (cip2 != null)
                        {
                            cip2 = _projectExplorerLink.MainFormLink.HierarchyForm.ShowFixedDimensionItemsDialog(cip2);
                            Assert.FailIfNot(rightpath.ParseElementAndApply("", Guid.Empty, cip2) == null, Assert.Id.Assert00062);
                        }
                        ConditionsDataGrid.EndEdit();
                        ConditionsDataGrid.CurrentCell = null;
                        break;
                    case 4:                    
                        //связь
                        _reason.SetConnectionByIndex(index, Reason.ParseConnection(s));                        
                        break;
                }                                
                RefreshCondition(index);
            }
        }

        /// <summary>
        /// Обработка изменения значения в одном из комбиков датагрида команд заключения
        /// </summary>
        private void ProcessConclusionCommandsDataGridDirty()
        {
            if (!programdirty)
            {
                programdirty = true;
                ConclusionCommandsDataGrid.EndEdit();
                programdirty = false;
                DataGridViewCell dvc_ = ConclusionCommandsDataGrid.CurrentCell;
                DataGridViewComboBoxCell dvc = dvc_ as DataGridViewComboBoxCell;
                int index = dvc.RowIndex;
                IConclusionCommand comm = _conclusion.GetItemByPosition(index);
                string s = dvc.Value as string;
                PathToValue leftpath = comm.PathToLeftValue;
                PathToValue rightpath = comm.PathToRightValue;                
                switch (dvc.ColumnIndex)
                {
                    case 1:
                        if (s.Equals(leftpath.ToStringUsingWithSituation(Guid.Empty)))
                            break;
                        FixedDimensionItemsPointer cip = leftpath.ParseElementAndApply(s, Guid.Empty, null);
                        if (cip != null)
                        {
                            cip = _projectExplorerLink.MainFormLink.HierarchyForm.ShowFixedDimensionItemsDialog(cip);
                            Assert.FailIfNot(leftpath.ParseElementAndApply("", Guid.Empty, cip) == null, Assert.Id.Assert00185);
                        }
                        ConclusionCommandsDataGrid.EndEdit();
                        ConclusionCommandsDataGrid.CurrentCell = null;
                        break;
                    case 2:
                        //команда может быть только одна - означивание
                        Assert.Fail(Assert.Id.Assert00063);
                        break;
                    case 3:
                        if (s.Equals(rightpath.ToStringUsingWithSituation(Guid.Empty)))
                            break;
                        FixedDimensionItemsPointer cip2 = rightpath.ParseElementAndApply(s, Guid.Empty, null);
                        if (cip2 != null)
                        {
                            cip2 = _projectExplorerLink.MainFormLink.HierarchyForm.ShowFixedDimensionItemsDialog(cip2);
                            Assert.FailIfNot(rightpath.ParseElementAndApply("", Guid.Empty, cip2) == null, Assert.Id.Assert00064);
                        }
                        ConclusionCommandsDataGrid.EndEdit();
                        ConclusionCommandsDataGrid.CurrentCell = null;
                        break;                    
                }
                RefreshConclusionCommand(index);
            }
        }

        /// <summary>
        /// Выбирает команду заключения
        /// </summary>
        /// <param name="index"></param>
        private void SelectConclusionCommand(int index)
        {
            DataGridViewRowCollection rows = ConclusionCommandsDataGrid.Rows;
            int c = rows.Count;
            for (int i = 0; i < c; i++)
            {
                rows[i].Cells[0].Value = (i == index) ? "V" : "";
            }
            SelectedConclusionCommandPosition = index;
        }

        /// <summary>
        /// Актуализирует информацию о ситуации-With
        /// </summary>
        private void ChangeWithSituation()
        {
            if (!programdirty)
            {
                string frname = WithComboBox.SelectedItem.ToString();
                Situation sit = _projectLink.GetFirstItemByName(frname);
                if (sit != null)
                {
                    _reason.WithSituationId = sit.Id;
                }
                else
                {
                    _reason.WithSituationId = Guid.Empty;
                }
                RefreshConditions();
            }
        }

        /// <summary>
        /// Выбирает условие посылки
        /// </summary>
        /// <param name="index"></param>
        private void SelectCondition(int index)
        {
            DataGridViewRowCollection rows = ConditionsDataGrid.Rows;
            int c = rows.Count;
            for (int i = 0; i < c; i++)
            {
                rows[i].Cells[0].Value = (i == index) ? "V" : "";                
            }
            SelectedConditionPosition = index;
        }        

        private void NewRuleDialog_Load(object sender, EventArgs e)
        {
            RefreshInfo();
        }

        private void ConditionsDataGrid_CurrentCellDirtyStateChanged(object sender, EventArgs e)
        {
            ProcessConditionsDataGridDirty();
        }

        private void ConditionsDataGrid_CellEndEdit(object sender, DataGridViewCellEventArgs e)
        {
            ConditionsDataGrid.EditMode = DataGridViewEditMode.EditOnKeystrokeOrF2;
        }

        private void ConditionsDataGrid_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            int row = e.RowIndex;
            if (row >= 0) //заголовки не обрабатываем
            {
                int col = e.ColumnIndex;
                if (col >= 1) //ячейку фокуса строки редактировать не надо
                {
                    DataGridViewCell cell = ConditionsDataGrid.Rows[row].Cells[col];
                    cell.Selected = true;
                    ConditionsDataGrid.CurrentCell = cell;
                    ConditionsDataGrid.BeginEdit(true);
                    ConditionsDataGrid.EditMode = DataGridViewEditMode.EditOnEnter;
                }
                SelectCondition(row);
            }
        }

        private void NewConditionButton_Click(object sender, EventArgs e)
        {
            AddCondition();
        }

        private void DeleteConditionButton_Click(object sender, EventArgs e)
        {
            DeleteCondition();
        }

        private void UpConditionButton_Click(object sender, EventArgs e)
        {
            UpCondition();
        }

        private void DownConditionButton_Click(object sender, EventArgs e)
        {
            DownCondition();
        }

        private void NewCommandButton_Click(object sender, EventArgs e)
        {
            AddConclusionCommand();
        }

        private void DeleteCommandButton_Click(object sender, EventArgs e)
        {
            DeleteConclusionCommand();
        }

        private void UpCommandButton_Click(object sender, EventArgs e)
        {
            UpConclusionCommand();
        }

        private void DownCommandButton_Click(object sender, EventArgs e)
        {
            DownConclusionCommand();
        }

        private void ConclusionCommandsDataGrid_CurrentCellDirtyStateChanged(object sender, EventArgs e)
        {
            ProcessConclusionCommandsDataGridDirty();
        }

        private void ConclusionCommandsDataGrid_CellEndEdit(object sender, DataGridViewCellEventArgs e)
        {
            ConclusionCommandsDataGrid.EditMode = DataGridViewEditMode.EditOnKeystrokeOrF2;
        }

        private void ConclusionCommandsDataGrid_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            int row = e.RowIndex;
            if (row >= 0) //заголовки не обрабатываем
            {
                int col = e.ColumnIndex;
                if (col >= 1) //ячейку фокуса строки редактировать не надо
                {
                    DataGridViewCell cell = ConclusionCommandsDataGrid.Rows[row].Cells[col];
                    cell.Selected = true;
                    ConclusionCommandsDataGrid.CurrentCell = cell;
                    ConclusionCommandsDataGrid.BeginEdit(true);
                    ConclusionCommandsDataGrid.EditMode = DataGridViewEditMode.EditOnEnter;
                }
                SelectConclusionCommand(row);
            }
        }

        private void WithComboBox_SelectedIndexChanged(object sender, EventArgs e)
        {
            ChangeWithSituation();
        }
    }
}
